package com.atguigu.gulimall.product;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
import org.springframework.cloud.openfeign.EnableFeignClients;

/**
 *  1、整合mybatis-plus
 *   1）、导入依赖（common中已导入）
 *   2）、配置数据源
 *      1.导入数据库的驱动——mysql connector（common中已导入）
 *      2.在application.yml中配置数据源相关信息
 *   3）、配置mybatis-plus
 *      1.使用@MapperScan
 *      2.配置主键自增
 *      3.告诉Mybatis-plus，sql映射文件位置（mybatis-plus.mapper-locations）
 *  2、逻辑删除
 *   1)、配置全局的逻辑删除规则（配置的和默认一样可省略）
 *   2）、配置逻辑删除的组件 Bean（3.1.1开始可省略）
 *   3）、给 Bean 加上逻辑删除注解 @TableLogic
 *  3、JSR303
 *   1）、给Bean添加校验规则注解:javax.validation.constraints,并定义自己的message提示
 *   2）、开启校验注解：@Valid
 *       校验错误后会有默认的响应
 *   3）、校验的Bean后紧跟 BindingResult 可以获取校验的结果
 *   4）、分组校验（多场景的复杂校验）
 *      1.给校验规则注解标注什么情况需要校验
 *      2.@Validated({AddGroup.class})
 *      3.默认没有执行分组校验注解@NotBlank，在分组校验情况下不生效，只会在@Validated时生效
 *   5）、自定义校验
 *      1.编写一个自定义的校验注解          com/atguigu/common/valid/ListValue.java:13
 *      2.编写一个自定义的校验器            com/atguigu/common/valid/ListValueConstraintValidator.java:8
 *      3.关联自定义的校验器和自定义的校验注解 validatedBy = {ListValueConstraintValidator.class} 【可以指定多个不同的校验器校验 】
 *  4、统一的异常处理
 *  @ControllerAdvice
 *   1)、编写异常处理类,使用RestControllerAdvice
 *   2)、使用@ExceptionHandler标注方法可以处理的异常
 *  5、模板引擎
 *   1）、thymeleaf-starter:关闭缓存
 *   2）、静态资源放在static文件夹下可直接访问
 *   3）、页面放在templates文件夹下可直接访问 xmlns:th="http://www.thymeleaf.org"
 *      SpringBoot访问项目的时候会默认找index
 *   4）、页面修改不重启服务器实时更新
 *      1）、引入dev-tools
 *  6、整合redis
 *   1）、引入 spring-boot-starter-data-redis
 *   2）、简单配置redis的host等信息
 *   3）、使用SpringBoot自动配置好的StringRedisTemplate来操作redis
 *  7、整合redisson作为分布式锁等功能框架
 *   1)、引入依赖 redisson
 *   2）、配置MyRedissonConfig
 *  8、整合SpringCache简化缓存开发
 *   1）、引入依赖 spring-boot-starter-cache
 *   2）、写配置
 *     自动配置
 *          CacheAutoConfiguration 引入的 RedisCacheConfiguration 自动配置好了 RedisCacheManager
 *     手动配置
 *          配置使用redis作为缓存 spring.cache.type:redis
 *   3)、测试使用缓存
 *      @Cacheable: Triggers cache population. 将数据保存到缓存的操作
 *      @CacheEvict: Triggers cache eviction.  将数据从缓存删除的操作
 *      @CachePut: Updates the cache without interfering with the method execution.不影响方法执行，更新缓存
 *      @Caching: Regroups multiple cache operations to be applied on a method.组合以上多个操作
 *      @CacheConfig: Shares some common cache-related settings at class-level.在类级别共享缓存的相同配置
 *      1）、开启缓存功能 @EnableCaching
 *   4）、Spring-Cache的不足
 *      1)、读模式
 *        缓存穿透：查询null                        解决：cache-null-values
 *        缓存击穿：大量并发同事查询一个正好过期的数据    部分解决：读数据时有加本地锁，写、删都无锁
 *        缓存雪崩：大量的key同时过期                 解决：加随机过期时间（存储是分散的，过期一般也是分散的）
 *      2）、写模式（缓存与数据库一致）
 *        读写加锁：
 *        引入Canal：感知MySQL更新，主动更新缓存
 *        读多写多：直接查询数据库
 *      3）、原理
 *        CacheManager->Cache(RedisCache) Cache负责缓存的读写
 *      4）、总结
 *        常规数据（读多写少，及时性、一致性要求不高的数据），可以使用Spring-Cache，写模式只要有过期时间
 *        特殊数据：特殊设计
 *
 */
@EnableDiscoveryClient
@SpringBootApplication
@EnableFeignClients(basePackages = "com.atguigu.gulimall.product.feign")
public class GulimallProductApplication {

    public static void main(String[] args) {
        SpringApplication.run(GulimallProductApplication.class, args);
    }

}
